package model_booleen;

import java.util.ArrayList;
import java.util.HashMap;

public class RechercheBooleanSimple {

    static private int nbMots = 0;
    static private BooleanSimple root;

    static public void buildQuery(String query) {
        root = null;
        nbMots = 0;
        BooleanSimple currentRoot = null;
        System.out.println(query);

        ArrayList<String> lstWords = new ArrayList<String>();
        String[] lstToken = query.split(" ");

        BooleanSimple currentParent = root;
        BooleanSimple b;
        nbMots = 0;

        root = buildTree(null, lstToken, 0, lstWords);

        System.out.println(" TREE ---  " + root);

        BooleanOperator.setQuery(lstWords);

    }

    static private BooleanSimple buildTree(BooleanSimple currentRoot,
            String[] lstToken, int j, ArrayList<String> lstWords) {
        BooleanSimple root = null;

        BooleanSimple currentParent = root;
        BooleanSimple b;
        nbMots = 0;

        for (int i = j; i < lstToken.length; i++) {

            // init de l'arbre
            if (i == j) {
                if (lstToken[i].contains("NOT")) {
                    root = new BooleanSimpleNot(lstToken[i]);
                } else if (lstToken[i].contains("(")) {

                    b = buildTree(currentParent, lstToken, i + 1, lstWords);
                    root = b;
                    currentParent = b;
                    i++;
                    int nbSubTree = 1;
                    while (nbSubTree > 0) {

                        if (lstToken[i].contains("(")) {
                            nbSubTree++;
                        } else if (lstToken[i].contains(")")) {
                            nbSubTree--;
                        }
                        i++;

                    }
                    if (i == lstToken.length) {
                        return root;
                    }


                } else {
                    root = new BooleanSimple(lstToken[i]);
                }

                currentParent = root;
                lstWords.add(lstToken[i]);

            } else {
                if (lstToken[i].contains("OR")) {

                    // MODIFICATION DE L ARBRE
                    b = new BooleanSimple(lstToken[i]);
                    b.addChildLeft(root);
                    root = b;
                    currentParent = b;

                } else if (lstToken[i].contains("AND")) {

                    // MODIFICATION DE L ARBRE
                    b = new BooleanSimple(lstToken[i]);
                    if (root.isLeaf() || lstToken[i - 1].contains(")")) {
                        b.addChildLeft(root);
                        root = b;
                        currentParent = b;
                    } else if (root.getClass() == BooleanSimpleNot.class) {
                        b = new BooleanSimple(lstToken[i]);
                        b.addChildLeft(root);
                        root = b;
                        currentParent = b;

                    } else {
                        currentParent.addChildRight(b);
                    }
                    currentParent = b;

                } else if (lstToken[i].contains("NOT")) {
                    b = new BooleanSimpleNot(lstToken[i]);
                    if (root.isLeaf()) {
                        b.addChildLeft(root);
                        root = b;
                        currentParent = b;
                    } else {
                        currentParent.addChildRight(b);

                    }
                    currentParent = b;
                } else if (lstToken[i].contains("(")) {

                    b = buildTree(currentParent, lstToken, i + 1, lstWords);
                    currentParent.addChild(b);
                    currentParent = b;
                    i++;
                    int nbSubTree = 1;
                    while (nbSubTree > 0) {
                        if (lstToken[i].contains("(")) {
                            nbSubTree++;
                        } else if (lstToken[i].contains(")")) {
                            nbSubTree--;
                        }
                        i++;
                    }
                } else {
                    currentParent.addChild(new BooleanSimple(lstToken[i]));

                    lstWords.add(lstToken[i]);

                    nbMots++;
                }

            }

        }
        System.out.println(root);
        return root;
    }

    static public double calculus(HashMap<String, Double> weights2) {

        BooleanSimple.setData(weights2);

        double result = root.calculus();
        System.out.println("   R  ==   " + result);
        return result;

    }
}
